<?php
/**
 * Description of x10_Manager
 *
 * @author prometheus
 */
abstract class x10_Manager extends ArrayObject
{
	////
	//// Class: x10_GeneralClass
	////

	/**
	 * Az objektum felhasználói elnevezése, rövid leírása.
	 * @var String
	 */
	public $xName = 'Általános célú kezelő';

	/**
	 * Az objektum beállításai
	 * @var x10_Config
	 */
	protected $config;

	////
	//// Class: x10_Manager
	////

	/**
	 * Az engedélyezett szolgáltatók listája.
	 * @var array of {@link Manager_ProvidersAcceptedDescriptor}
	 */
	protected $providersAccepted = array();
	
	/**
	 * Konstruktor.
	 * @param x10_Config $config
	 */
	public function __construct(x10_Config $config=NULL)
	{
		parent::__construct();
		$this->config = $config;
		if (is_null($this->config))
		{
			$this->config = new x10_Config($this);
		}
	}

	/**
	 * Módosítja a beállításokat.
	 * @param x10_Config $config
	 * @return Provider
	 * @throws E_Provider_ConfigNotExists
	 * @throws E_Provider_ConfigParseError
	 */
	public function setConfig(x10_Config $config)
	{
		$this->config = $config;
		return $this;
	}

	/**
	 * Visszatér a beállításokkal.
	 * @return x10_Config
	 */
	public function getConfig()
	{
		return $this->config;
	}

	/**
	 * Regisztrál egy engedélyezett elem szolgáltatót a kapott leíró alapján.
	 * 
	 * @param x10_Provider_Descriptor $descriptor
	 * @return Manager
	 */
	public function registerProvider(x10_Provider_Descriptor $descriptor)
	{
		$this->providersAccepted[$descriptor->className] = $descriptor;
		return $this;
	}

	/**
	 * Ellenőrzi egy felfűzni való elem érvényességét.
	 * 
	 * @param x10_Provider $item
	 * @param Bool $enableExceptions
	 * @return Bool
	 * @throws x10_E_Manager_InvalidItemProvider
	 * @throws x10_E_Manager_InvalidItemProviderType
	 */
	public function validateItem($item, $enableExceptions=FALSE)
	{
		$result = $this->validateItemProvider($item);
		if ($enableExceptions and !$result)
		{
			if (is_object($item))
			{
				throw new x10_E_Manager_InvalidItemProvider($this->xName, get_class($item));
			}
			else
			{
				throw new x10_E_Manager_InvalidItemProviderType($this->xName);
			}
		}
		return $result;
	}

	/**
	 * Ellenőrzi egy elem szolgáltatójának érvényességét.
	 * 
	 * @param x10_Provider $item
	 * @return Bool
	 */
	protected function validateItemProvider($item)
	{
		$result = FALSE;
		if (is_object($item))
		{
			$cls = get_class($item);
			if (!array_key_exists($cls, $this->providersAccepted))
			{
				foreach ($this->providersAccepted as $descriptor)
				{
					if (!$descriptor->restricted and $item instanceof $descriptor->className)
					{
						$result = TRUE;
						break;
					}
				}
			}
			else
			{
				$result = TRUE;
			}
		}
		return $result;
	}

	////
	//// Class: ArrayObject
	////

	public function append($value)
	{
		if ($this->validateItem($value, TRUE)) parent::append($value);
	}

	public function offsetSet($index, $newval)
	{
		if ($this->validateItem($newval, TRUE)) parent::offsetSet($index, $newval);
	}
}
?>
